package Compress;

import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.io.IOUtils;
import org.apache.hadoop.io.compress.CompressionCodec;
import org.apache.hadoop.io.compress.CompressionCodecFactory;
import org.apache.hadoop.io.compress.CompressionInputStream;
import org.apache.hadoop.io.compress.CompressionOutputStream;
import org.apache.hadoop.util.ReflectionUtils;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;

public class TestCompress {
    public static void main(String[] args) throws Exception {
        //压缩方法
//        compress("F:\\date\\Sogou.txt","org.apache.hadoop.io.compress.GzipCodec");
        //解压缩
        decompress("F:\\date\\Sogou.txt.gz", ".txt");
    }

    /**
     * 解压缩
     *
     * @param 文件路径+文件名
     * @param 后缀
     */
    private static void decompress(String fileName, String decoded) throws Exception {
        //获取实例
        CompressionCodecFactory factory = new CompressionCodecFactory(new Configuration());

        CompressionCodec codec = factory.getCodec(new Path(fileName));

        //压缩的输入
        CompressionInputStream cis = codec.createInputStream(new FileInputStream(new File(fileName)));

        //文件输出
        FileOutputStream fos = new FileOutputStream(new File(fileName + decoded));

        //流拷贝
        IOUtils.copyBytes(cis, fos, 5 * 1024 * 1024, false);

        //关闭流
        fos.close();
        cis.close();

    }

    /**
     * 压缩方法
     *
     * @param 文件路径+文件名
     * @param 编/解码器
     */
    private static void compress(String fileName, String method) throws Exception {
        //创建文件输入流
        FileInputStream fis = new FileInputStream(new File(fileName));

        //通过反射找到编/解码的类
        Class codeClass = Class.forName(method);

        //通过反射工具类找到编码器对象 & conf配置
        CompressionCodec codec = (CompressionCodec) ReflectionUtils.newInstance(codeClass, new Configuration());

        //创建文件输出流
        FileOutputStream fos = new FileOutputStream(new File(fileName + codec.getDefaultExtension()));

        //获得编码器输出对象
        CompressionOutputStream cos = codec.createOutputStream(fos);

        //流拷贝  是cos不是fos
        IOUtils.copyBytes(fis, cos, 5 * 1024 * 1024, false);

        //关闭流
        cos.close();
        fos.close();
        fis.close();
    }
}
